Cryptological attacks are known. Examples of such attacks include side channel attacks, which make it possible to compromise the security of an information system based on the measurement of a physical signature of this system when it is operating. This physical signature can comprise one or more physical characteristics of the system, such as emitted electromagnetic radiation, delays between the execution of two instructions, or electrical power levels consumed by the system.
For example, an attack by power analysis (such as those known by the terms “simple power analysis”, “differential power analysis”, “correlation power analysis”) makes it possible to determine the behavior of a computer program executed by a processor by measuring the electrical power consumed by the processor as it executes these instructions. Such attacks can be used to steal encryption keys during the operation of a cryptographic system. It is therefore desirable to be able to prevent such attacks.
There are methods for executing a computer program in such a way as to reduce the vulnerability to such attacks. These methods comprise, for example, the execution, by a microprocessor, of a polymorphic binary code of a predetermined function.
A polymorphic binary code is a binary code that changes form when it is executed by a microprocessor. This means the code changes form on each execution. “Change of form” means that the instructions executed by the microprocessor are different even if the input and output data processed by the binary code remain the same. The instructions are different if, after the same number of cycles of the microprocessor, the opcode, or the operand or operands, or even the literal values of the instruction executed are not the same. Such a method is described in the article by Giovanni Agosta et al., “A code morphing methodology to automate power analysis countermeasures”, Proceedings of the 49th Annual ACM/IEEE Design Automation Conference (DAC'12), pages 77-82, June 2012.
This method does, however, present drawbacks. In particular, its implementation requires significant computational resources, in terms of computation cycles or memory needs. Its implementation also requires an ad hoc static compiler. This method can therefore be difficult to implement in systems having limited resources, such as embedded systems or chip cards, and furthermore demands the use of a dedicated compiler. In practice, this is costly if numerous processor architectures have to be supported.
As noted above, the known method comprises a dedicated static compiler. This compiler functions in the same way as a traditional compiler. However, it has been modified to extract, from the source code, “fragments” that are identified in the source code by specific attributes, or “pragmas.”
The fragments are the parts of the binary code intended to be processed by the polymorphic engine described below. The fragments express the production of a function of the source code in one or more machine instructions expressed in a standardized manner by the static compiler. The standardization includes replacing the operands of the instructions, such as register identifiers or literal values, with symbolic constants.
The method comprises a polymorphic engine intended to be run during the execution of the compiled application (runtime) by the target processor. During execution, the polymorphic engine selects, for each fragment, the target instruction or instructions intended to be executed by the microprocessor to perform the predetermined function. These target instructions are selected by choosing a coding variant of pre-existing instructions contained in a dictionary of equivalences embedded in the binary code. The polymorphic engine and the dictionary of equivalences are constructed during the static compilation phase, before the execution of the binary code, using the ad hoc compiler described above.
The polymorphic engine works by applying the following steps to process each fragment to perform a specific set of target instructions to perform the predetermined function:                search for and select, in a dictionary of equivalences constructed during the static compilation phase, a set of instructions semantically equivalent to the standardized instruction;        destandardize the selected set of instructions, by replacing the symbolic constants with immediate values; and        evaluating the literal values contained in the operands.        
The operating mechanism of such a polymorphic engine is described in more detail in Section 3.1 of the article by Agosta et al., cited previously.
As an example, the operation of this polymorphic engine will be illustrated using the fragment “AND R0, R1, #0”. This fragment, which is represented here in machine language, or assembly language, performs a logical “AND” between the value contained in the register “R1” and an immediate value “0”, and stores the result in the register “R0”. The polymorphic engine acquires this instruction then performs certain operations to select a variant of this instruction.
In particular, to select a variant of the instruction, the polymorphic engine engages in a search step during which it searches the dictionary of equivalences for the different blocks of instructions equivalent to the “AND” operation by using the name of the operation “AND” as a search key. These blocks are made up of one or more instructions expressed in machine language. Next, the polymorphic engine randomly selects one of these equivalent blocks of instructions. During the random selection from the different blocks of equivalent instructions, it is assumed here that the following set of instructions, which is semantically equivalent to the “AND R0, R1, #0” instruction, is selected in the dictionary of equivalences from other semantically equivalent blocks:                AND R0, R1, (#0 XOR const1)        AND R2, R1, (#0 XOR const2)        AND R0, R0, R2in which “R2” is a previously emptied intermediate register, and in which “const1” and “const2” are two additional symbolic constants such that the value of “const2” is the logical opposite of the value of “const1”.        
Then, during the standardization step, immediate values are assigned to the symbolic constants and to the registers that had been replaced during the standardization step.
Thus, the polymorphic engine makes it possible to randomly generate variants for the fragments identified by the programmer, and extracted by the static compiler. The instructions associated with each variant by the polymorphic engine can be executed by the microprocessor without modifying the function of the program.
The semantic equivalences, or variants, are stored in a dictionary of equivalences defined during the compilation of the binary code. This compilation is performed from a source code of a computer program. Typically, such a program comprises a plurality of predetermined functions that are distinct from one another. Each of these predetermined functions is performed, in the compiled binary code, by one or more predetermined instructions. Since the dictionary of equivalences is constructed once and for all during the compilation, it has to contain the variants of all the predetermined instructions performing each of these functions. Such a dictionary therefore has a significant size.
The dictionary of equivalences, which is quite large, is then loaded in its entirety into memory each time the microprocessor executes a portion of the binary code that corresponds to one of the predetermined functions of the source code. Because of the design of the code generator, these portions of the binary code each have to invoke the dictionary of equivalences during their execution, despite the fact that some of the variants contained in this dictionary of equivalences are not suitable for use as variants for the predetermined function described by the particular portion of binary code. Furthermore, the execution of the steps of standardization and of search for equivalences to modify each instruction requires a significant number of compilation cycles. The foregoing method thus presents numerous drawbacks.
Also known is the method described in Antoine Amarilli et al., “Can code polymorphism limit information leakage?”, WISTP 2011, Lecture Notes in Computer Science, vol. 6633, p. 1-21, Springer, 2011. This method describes the execution of a polymorphic binary code. In it, the polymorphism introduced is limited to the reorganization of the instructions of the binary code, separated into buckets for the analysis of the sequence followed by the program and the variants likely to be introduced. This method has been demonstrated only in a Scheme implementation, in which the rewriting of the program is performed by a “source-to-source” approach.
Furthermore, the above method requires significant computational resources for its execution, in part for the same reasons as the method of Agosta et al. This method also has the drawback of requiring a medium for Scheme in the embedded systems or in the chip cards that are commonly used.
Also known from the prior art are EP2343663 A1 (GEMALTO), and Cristoph Herbst et al., “An AES Smart Card Implementation Resistant to Power Analysis Attacks”, ACNS 2006, LNCS 3989, p. 239-252, Springer, 2006.